home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Merciful 4
/
Merciful - Disc 4.iso
/
software
/
p
/
psychotoads.dms
/
psychotoads.adf
/
a1516
< prev
next >
Wrap
Text File
|
1989-03-31
|
52KB
|
1,508 lines
15: BACKGROUND GRAPHICS 207
------------------------------
Nowadays, it's not uncommon for an arcade game to contain hunderds of
different screens. With compaction, it's possible to crap a single 32
colour screen into about 30k of memory. So 100 screens would be the
equivalent of about 3 Megabytes of data. Imagine how difficult this
would be to fit into a standard A500!
The classic way of avoiding this restriction, is to construct your
backgrounds out of a set of simple building blocks. Once these "tiles"
have been created, they can be placed on the screen in any order you
like. So the same set of tiles can be reused to generate a vast number
of potential screens. Each screen is now stored as a simple list of its
components, and requires a tiny fraction of the original memory.
In order to exploit this system, you'll obviously need some way of
defining your various screen maps. As you might have guessed, we've
helpfully provided you with a powerful map definer accessory on the
AMOS program disc. Full details can be found in the accompanying
documentation file.
AMOS Basic also includes a number of special instructions for drawing
your tiles on the screen. These make it easy to generate the fast
scrolling backgrounds that are the hallmark of a modern arcade game.
Icons
=====
Icons are separate images which have been especially designed for
producing your background screens. Once you've drawn an icon, it's
fixed permanently into place. So you can't move it to a new position
using the AMAL animation system.
All icons are stored in their own AMOS memory bank (#2). This bank is
created using the Sprite definer accessory (on the AMOS Program disk),
and will be automatically saved along with your Basic programs.
Like Bobs, Icons are displayed using the Amiga's amazing Blitter
chip. But since Icons are essentally static objects, they are usually
drawn in REPLACE mode. Your icons will therefore totally erase any
existing graphics at the current screen position.
PASTE ICON (draw an icon)
PASTE ICON x,y,n
Draws icon number n on the screen at GRAPHIC coordinates x,y. n is the
number of the icon which is to be displayed. This must have been
previously stored in the ICON bank.
Icons can be freely positioned anywhere on the screen, subject to the
normal clipping rules. Example:
Load "AMOS_DATA:Icons/Map_icons.abk"
Screem Open 0,320,256,32,Lowres : Cls 0 : Get Icon Palette
For X=1 To 11 : Paste Icon X*32,0,1 : Next X
For Y=1 To 6 : Paste Icon 0,Y*32+11 : Paste Icon 288,Y*32,1
Next Y
For X=1 To 11 : Paste Icon X*32,223,1 : Next X
Note that if you're using double buffering, a copy of your icons will
be drawn into both the physical and logical screens. Since this is
rather slow, it's common practive to add a call to AUTOBACK 0 before
drawing your icons on the screen. This restricts straight to the
physical screen using SCREEN COPY, saving a considerable amount of
time.
For a further example, see the MAPVIEW program on the AMOS DATA disc.
This displays a background screen you've created using the AMOS Map
Editor.
GET ICON (create an icon) 208
GET ICON [s,] i,tx,ty TO bx,by
Captures an image from the screen and loads it into icon "i". If this
icon does not presently exist, it will be created for you in bank 2.
This bank will be automatically reserved by the system if required.
i is the number of your icon, starting from 1. tx,ty to bx,by define
the rectangular zone which encloses the selected region.
s determines the number of the screen which will be used as the
source of your image. If it's omitted, the image will be taken from the
current screen instead. Example:
Erase 2
F$=Fsel$("*.*","","Load a screen") : If F$="" Then Direct
If Exist(f$) Then Load Iff f$,0 Else Direct
SH=Screen Height : H=SH/32-1 : SW=Screen Width : W=SW/32-1
For Y=0 to H
For X=0 to W
Get Icon X+Y*W+1,X*32,Y*32 To X*32+31,Y*32+31
Next X
Next Y
Cls 0
Do
Paste Icon Rnd(Sw-1),Rnd(SH-1),Rnd/(H*W)+1
Loop
GET ICON PALETTE (get icon colours)
GET ICON PALETTE
Grabs the colours of the icon images in bank 2, and loads them into the
current screen palette. This command is normally used to initialize the
screen after you'be loaded some icons from the disc. Example:
Load "AMOS_DATA:Icons/Map_icons.abk"
Get Icon Palette
Paste Icon 100,100,1
DEL ICON (deletes icons) 209
DEL ICON n[ TO m]
Deletes one or more icons from the icon bank. n is the number of the
first icon to be removed.
m is the optional number of the last icon to be deleted in the list.
If it's included all the icons from first to last will be erased one
after another.
When the final icon in a bank has been deleted, the entire bank will
be removed from memory.
MAKE ICON MASK (set colour zero to transparent)
MAKE ICON MASK [n]
Normally, any icons you draw on the screen will completely replace the
existing background. The icon will seem to be displayed in a
rectangular box filled with colour zero.
If you want to avoid this effect and overlay your icons directly over
the current graphics, you'll need to create a *mask* for your icons.
This informs AMOS that colour zero should be treated as transparent.
n is the number of the icon to be affected. If it's omitted, a mask
will be defined for all icons in the bank. See EXAMPLE 15.1
Screen blocks
=============
AMOS Basic supplies you with a set of powerful BLOCK commands which
allow you to grab part of an image into memory and paste it anywhere on
the screen.
These instructions are mainly used for holding temporary data,
since your blocks cannot be saved along with your Basic programs.
Blocks are especially effective in the construction of dialogue
boxes, as they can be used to save the background areas before
displaying your new graphics.
They can also be exploited in puzzle games like Split Personalities.
Each block can be loaded with a single section of your image. You can
then jumble your pictures by rearranging the blocks on the screen with
PUT BLOCK.
GET BLOCK (grab a screen block into memory)
GET BLOCK n,tx,ty,w,h[,mask]
GET BLOCK grabs a rectangular area in block number n, starting at
coordinates tx,ty.
n is the number of the block ranging from 1-65535. tx, ty set the
coordinates of the top left hand corner of your block. w,y hold the
width and height of the block respectively.
"mask" is a flag which chooses whether a mask will be created for
your new block.
mask=0 Replace mode. When the block is drawn on the screen,
it will totally destroy any graphics at that current
position.
mask=1 Calculates a mask for the block. Colour zero will now
be treated as if it were transparent.
PUT BLOCK (copies a previously created 210
block onto the screen)
PUT BLOCK n[,x,y]
PUT BLOCK n,x,y,planes[,minterms]
PUT BLOCK copies block number n to the current screen. x,y specify the
position of your new block on the screen. If they are omitted the block
will be redrawn at its original screen coordinates.
Note that all drawing operations will be clipped to fit into the
current screen, starting from the nearest 16 pixel boundary.
For a demostration of the BLOCK commands see the routine in EXAMPLE
15.2. We've also provided experienced programmers with a couple of
optional extras. These are not needed for the vast majority of
applications, they're only required when you want to achieve weird
special effects on the screen!
"planes" holds a bit-map which sets the range of colours which will
be drawn in your block. The Amiga's screen is divided up into segments
known as bit-planes. Each plane contains a single bit for every point
on the Amiga's screen. When the Amiga's hardware displays this point,
it combines the bits from each plane to calculate the required colour
number. Each bit in "planes" represents the status of a single
bit-plane. If it's set to one, then the selected plane will be drawn by
the instruction, otherwise it will be completely ignored. The first
plane is represented by bit zero, the second by bit one, etc.
Usually, the block will be displayed in all the available bit-planes.
The corresponds to a bit-pattern of %111111
"minterm" selects the blitter mode used to copy your block on the
screen. A full description of the possible drawing modes can be found
in the section on SCREEN COPY. The best way to loearn about these
options is to experiment!
DEL BLOCK (delete a screen block)
DEL BLOCK n
Deletes one or more blocks and restores the memory used to AMOS Basic.
DEL BLOCK Erases *all* current blocks
DEL BLOCK n Deletes block number n.
GET CBLOCK (save and compact a screen image) 211
GET BLOCK n,x,y,sx,sy
The GET BLOCK command saves and compacts a rectangular area of the
screen. The compaction system used by this command has been especially
optimized for speed. So it's nowhere near as efficient as the dedicated
AMOS compression routines provided by the PACK or SPACK instructions.
CBLOCKS are often used to grab the area underneath your dialogue
boxes. After the dialogue has been completed, the screen can quickly
restored back to its original state. See EXAMPLE 15.3.
n specifies the number of your block and can range between 1-65535.
x,y are the top left coordinates. The x coordinate is rouded to the
nearest multiple of 8.
w,h hold the dimensios of the area to be saved. The width is always
rounded to an exact multiple of 8.
PUT CBLOCK (displays a block
created using CBLOCK)
PUT CBLOCK n [,x,y]
Places block n on the current screen at coordinates x,y. If the target
coordinates are omitted, the block will be redrawn at its original
screen position. Also note that x is automatically rounded to the
nearest eight pixel boundary.
DEL CBLOCK (deletes a screen block
defined with GET CBLOCK)
DEL CBLOCK [n]
Erases all blocks from memory. If n is present only block n will be
deleted.
16: MENUS 212
---------------------------
If you've used the Amiga for some time you'll already be familiar with
the idea of menus. Impossible as it seems, AMOS has taken the existing
system and improved it almost beyond recognition.
Menus can be created with up to eight separate levels, and each
individual menu item can be repositioned on the screen at will. Menu
titles can be printed in any combination of colours or styles. You can
also include bobs or icons directly in your menus using an amazing menu
definition language.
AMOS Basic is equally impressive when it comes to reading a menu.
There's a buit-in interrupt-dricen ON MENU command which can
automatically branch to a selected point in your program depending on
the option selected. Furthermore, any menu option can be accessed
directly from the keyboard using the MENU KEY instruction.
For a demonstration of the terrific effects that can be achieved with
this system, load the program EXAMPLE 16.1.
Using a menu
============
All AMOS menus are called up by holding down the right mouse button in
the standard way. Once a menu has been activated you can then select an
option directly with the mouse cursor. When you release the button, the
option number you have chosen will be returned to your program.
Menus can be repositioned by placing the mouse cursor over the top
left corner of an item and holding down the LEFT button. A small box
will now appear on the menu bar which can be dragged across the screen
using the mouse.
In addition, holding down the SHIFT key will freeze a menu into
place. This allows you explore a menu without selecting any of the
various options. You can also use any of the mouse features such as
slowing or axis selection in conjunction with your menus.
Creating a simple menu
======================
AMOS menus can be created either directly within your programs or using
a special menu definer included on the AMOS program disc.
If you've never used menus before, the sheer variety of the available
menu commands may seem a little overwhelming. Here's a brief
description of the basic features to provide you with a painless
introduction to AMOS menus.
Setting the title line
----------------------
The first stage in the creation of a menu is to define the "title
line". THe title line of a menu can be set using the MENU$ command. In
its simplest form this has the format:
MENU$ (set a menu title)
MENU$(n)=title$
MENU$ creates a title line for your menu. Each heading is assigned it's
own individual number starting from one, and increasing from left to
right. So the leftmost title is repsresented by a one, the next title
as two, etc.
The text in "title$" holds the name of the option which will be
displayed in your new menu. Here is a simple example which constructs a
menu line consisting of just two titles: ACTION and MOUSE
Menu$(1)=" Action "
Menu$(2)=" Mouse "
Note the space after "Action" - this will separate it from Mouse, the
next menu along. You must now specify a list of options to be 213
associated with each of your new headings. These form a vertical bar
which will drop into place whenever a title is selected with the mouse.
MENU$(t,o) (set a menu option)
MENU$(t,o)=option$
This second form of MENU$ defines a set of options which will be
displayed in the menu bar.
t is the number of menu heading which your option will displayed
under. o is the option number you with to install in the menu bar.
All options are numbered downwards from the top of the menu, starting
from one.
The only physical limit to the size of your menu is the amount of
memory, but it's wise to restrict yourself to less than about 10
options for each title. This will keep the complexity of your menus
down to an agreeable minimum.
"option$" holds the name of your new option. This can consist of any
section of text you like. For an example, try adding the following
lines to the program above:
Rem Action menu
Menu$(1,1)=" Quit "
Rem Mouse menu
Menu$(2,1)=" Arrow "
Menu$(2,2)=" Pointer "
Menu$(2,3)=" Clock "
Wait Key
This specifies a list of alternatives for the ACTION and the mouse
menus. If you try to run this program as it stands, nothing will
happen. That's because the menus need to be initialised with a call to
the MENU ON command. Enter this thin above program before the Wait Key
instruction. Now run the example and select the menu items with the
mouse cursor. Remember to hold down the RIGHT mouse button first!
MENU ON (activate menu)
MENU ON
Activates a menu defined using the MENU$ command. The menu line will
now appear automatically when the right mouse button is pressed ny the
user. To start the previous menu, insert the following line after the
definition statements.
Menu On
Go to the Direct window and play around with the menus. Select options 214
by pressing the right mouse button
Reading a simple menu
=====================
Once you've created your menu and activated the AMOS menuing system
you'll want to discover which options have been selected by the user.
This can be accomplished using a simple form of the CHOICE command.
=CHOICE (read a menu)
selected=CHOICE
CHOICE returns a value of -1 (true) if the menu has been highlighted by
the user, otherwise 0. It's automatically reset to 0 after each test.
It's also possible to find the title number which has been selected
using a second form of this instruction.
heagind=CHOICE(1)
"heading" now contains the number of the "title" which has been
highlighted by the user. Similarly you can retrieve the actual option
number which has been chosen with a parameter of two.
item=CHOICE(2)
Try adding the following lines to the previous example:
Do
Rem If choice=-1 can be simplified to: If choice, as seen...
If choice and choice(1)=1 Then Exit
If choice(1)=2 and choice(2)<>0 Then Change Mouse choice(2)
Loop
This changes the shape of the mouse cursor depending on which option
you have chosen from the menu. A full demonstration of these menu can
be found in the file EXAMPLE 16.2.
Advanced menuing features
-------------------------
We will now cover some of the more advanced menuing features available
from within AMOS Basic. Used properly these AMOS menus can add a whole
new dimension to your programs.
MENU$ (create a menu) 215
MENU$(,,)=normal$[,selected$][,inactive$][,background$]
Defines the appearance of each individual menu item in one of your
menus. Unlike normal Amiga menus these items are not restricted to
standard text. They can also include embedded commands which allow you
to draw bobs, icons or graphics at any point in the menu line.
Any of the parameters in this instruction may be optionally omitted,
so you can change parts of a menu description indenpendently. A value
of "" in your menu string will ERASE the existing setting. Similarly
you can retain the original value by including a comma at the
appropriate point. For example:
Menu$(1)=" Action ","" : Rem Erase second option
Menu$(2)=" Mouse 2 ",, : Rem Change title without altering
anything else.
The position of the menu item within the actual menu is indicated using
a list of up to eight parameters separated by commas. The general
format is:
(item)/(item,option)/(item,option,sub option)...
"normal$" is a string which sets the normal appearance of an item when
it's displayed in the menu. "selected$" changes the effect of
highlighting a menu option with the mouse. As a default, selected items
are printed in inverse text.
"inactive$" changes the appearance of an item which has been
deactivated using the MENU INACTIVE command. If this string is omitted,
all inactive imtes will be displayed in italics. "background$" creates
a background for your menu items when they are initially drawn.
Generally this will be a bo of some sort created with the internal Bar
or line commads.
For now one, we'll abbreviate these parameters using a standard
notation:
setting$=[,selected$][,inactive$][,background$]
The menu hierarchy
------------------
The level of an item in the menu is determined by its position in the
menu hierarchy.
Menu$(1)="Title"
Menu$(1,1)="Option 1"
Menu$(1,2)="Option 2"
Menu$(1,2,1)="Item 1"
This defines a simple menu. The structure of a menu is similar to that
of an array. Each level of the menu is represented by its own dimension
in the array, and is controlled using a separate version of the MENU$
command.
The first level represents the title line which appears at the top of
your menus. It can be set using a command like:
Menu$(n)=title$[setting$]
"n" now corresponds to the position of the title from the left of the 216
screen, and setting$ refers to the three optional strings which define
the general appearance of the menu. It's important to define the title
of your menus first as this *dimensions* the array. All other items may
be created in any order you wish.
Each title is associated with a list of menu options which drop into
view when the menu is selected. These form the second level of the menu
structure and are defined using a second version of the MENU$ command.
Menu$(n,option)=Item$[setting$]
"option" holds the number of the item measured from the top left of the
menu bar. There's no limit to the number of options which may be linked
to a single title, other than the amount of available memory.
Each individual option can in turn be associated with its own sub
menus up to a total of eight levels.
Menu$(n,option,sub option)=Item$[setting$]
Once you've created a menu it can be expanded or changed at any point
in your program. Never change the current screen while you are creating
a menu as this will lead to an error message.
See EXAMPLE 16.3
=CHOICE (read menu)
item=CHOICE[(dimension)]
The CHOICE function checks whether an option has been highlighted on
the current menu. If an item has been selected (down to the lowest
level), CHOICE will return a value of -1, otherwise it will be 0. After
you've called this function, the status of the menu will be
automatically restored to 0 (false). This stops a single menu access
from being accidentally detected several times.
The second form of this command returns the option selected at the
required level.
item=CHOICE(dimension)
"dimension" indicates the level of the menu which is to be read. As you
may recall, a level number of 1 corresponds to the title line of the
menu. Similartly the levels between 2 and 8 indicate the number of an
ioption which has been chosen. If a menu item has not been selected,
"item" will be loaded with a value of zero. For example:
Menu$(1)="Menu"
Menu$(1,1)="Option 1"
Menu$(1,2)="Option 2"
Menu$(1,2,1)="Option 2.1"
Menu On
Do
If choice Then Print choice(1),choice(2),choice(3)
Loop
If you wanted to implement larger menus with this system, your program
would need to use a long list of IF...THEN statements to deal with each
and every possibility. This would cause a small but significant delay
in your program while the menus were being read. It would also make it
very difficult to amend your program later. Fortunately AMOS Basic
provides you with a painless method of managing even the largest menus.
ON MENU PROC (automatic menu selection) 217
ON MENU PROC proc1 [,proc2,...]
Each title in your menu can be assigned its own procedure which will be
executed automatically whenever an option is selected by the user. The
action of this command is similar to the code below:
If Choice
If Choice(1)=1
Proc1
Endif
If Choice(1)=2
Proc2
Endif
: : :
: : :
Endif
There is one crucial difference between the ON MENU command and the
above instructions. ON MENU is performed 50 times a second using
interrupts and does not affect the overall running of your program.
This means that your program can be doing something totally different
while the menus are being checked by the system.
Whenever the user selects a menu item the required procedure will be
immediately executed with no further ation on the part of your program.
Your procedure can then use the CHOICE command to find which option has
been chosen and perform the appropriate action.
After the procedure has concluded, your program will be returned to
the instruction following the ON MENU call. Here's an example:
Menu$(1)="Action" : Menu$(1,1)="Count" : Menu$(1,2)="Quit"
Menu On : Rem Activate menu
On Menu Proc ACTION
On Menu On : Rem Activate On Menu command
Do
X$=Inkey$ : If X$<>"" Then Print X$;: Inc W
Loop
Procedure ACTION 218
Shared W
If Choice(2)=1
Locate 0,0 : Print "You typed ";W;" letters" : W=0
On Menu On : Rem Initialise menus
Endif
If Choice(2)=2 Then Edit
End Proc
There are a couple of important points to note about this example.
Firstly, see how the on menu sequence is activated using the ON MENU ON
command. This *must* be called after the menu handling procedure has
finished as it's needed to restart the menuing system. Also note the
use of INKEY$ rather than INPUT. The INPUT command will halt the menu
checks while you are entering a line. All other commands can be used
without problems, including WAIT, WAIT VBL and WAIT KEY. For a further
example see EXAMPLE 16.4
ON MENU GOSUB (automatic menu selection)
ON MENU GOSUB label1 [,label2,...]
Enters one of a list of subroutines depending on the option which has
been selected by the user. Once you've called this command and created
your subroutines, the menus will be checked automatically 50 times a
second.
Note that each title on the menu line is handled by its own
individual subroutine. This differs from its AMIGA Basic equivalent
which controls the entire menu with just a single routine.
After using this command you should activate the menuing system with
a call to the ON MENU. The menus must be reinitialised in this way
before jumping back to the main program with RETURN. Also note that
label *MAY NOT* be replaced by an expression as the label will only be
evaluated once when the program is run.
ON MENU GOTO (automatic menu selection)
ON MENU GOTO label1 [,label2,...]
This command has now been superceded by the more powerful ON MENU PROC
and ON MENU GOSUB instructions. It's intended to provide compability
with programs written in STOS Basic. WHen ever a menu is selected, the
program wlil jump to the appropriate label.
ON MENU ON/OFF ([de]activate automatic
menu selection)
ON MENU ON
Activates the automatic menuing system created by the ON MENU
PROC/GOSUB/GOTO commands. After a sub-routine has been accessed in this
way, the system will be DISABLED. So it's vital to reactivate the
system with ON MENU ON before returning to the main program.
ON MENU OFF
This temporarily freezes the automatic menuing system. It's useful when
your program is executing a procedure which needs to be performed
without interruptions - such as loading and saving information to the
disc. The menus can be reactivated using ON MENU ON.
ON MENU DEL (dlete the labels used by ON MENU) 219
ON MENU DEL
This erases the internal list of labels or procedures created by the ON
MENU commands. You can now redirect your menus to another part of your
program using a further call to ON MENU. WARNING! Only use this command
after you've deactivated the menus with ON MENU OFF.
Keyboard shortcurs
------------------
Despite the undoubted appeal of menus, some users prefer to call up the
options of a program straight from the keyboard. Althought menus are
certainly easy for beginners, once you've familiarised yourself with a
program it can be much faster to call up an option from the keyboard.
AMOS Basic allows you to assign a keyboard shortcut to any of your
menu items. These keystrokes are interpreted exactly as if the user had
accessed the equivalent option from the menu. They can be used with any
of the AMOS Basic menuing commands, including ON MENU.
MENU KEY (assign a key to a menu item)
MENU KEY(,,) TO c$
MENU KEY(,,) TO scan[,shift]
This allows you to assign any key to any item in a previously defined
menu. The only restriction is that item you have specified must be at
the bottom level of our menu. So you can't use a shortcut to select a
sub menu as each command must correspond to a single option in the
menu.
c$ is a string containing a single character which is to be assigned
to the menu option. Any additional characters in the string will be
ignored.
Each key on the Amiga's keyboard is assigned its own individual
scancode. By using this code you can assign keys to a menu which have
no Ascii equivalents. Here is a list of scancodes which can be used
with your menus.
Scancode Keys
-------- ----
80 - 89 Function keys F1-F10
95 Help
69 Esc
"shift" is an optional bitmap which allows you to check for control key 220
combinations such as ALT+HELP or CONTROL+D. The format of "shift" is:
Bit Key Tested Notes
--- ---------- -----
0 Left SHIFT Only one shift key can be tested at a time
1 Right SHIFT
2 Caps Lock Either ON or OFF
3 CTRL
4 Left ALT
5 Right ALT
6 Left AMIGA C= key on some keyboards
7 Right AMIGA
Note that if you set more than a single bit in this pattern, you'll
have to press several keys simultaneously to call up your menu item.
Any of these short-cuts can be deactivated by using MENU KEY with no
parameters. For example:
Menu Key(1,10)
With the help of MENU KEY command, adding shortcuts to a menu is a
trivial operation, so you are strongly recommended to include them as
standard in your programs. Here is an example that checks for the
Amiga's 10 function keys:
Menu$(1)=" Function Keys "
For A=1 To 10
OPT$=" F"+Str$(A)+" "
Menu$(1,A)=OPT$
Menu Key(1,A) To 79+A
Next A
Menu On
Do
If Choice Then Print "You pressed function key ";Choice(2)
Loop
Menu control commands
---------------------
MENU ON (activate a menu)
MENU ON [bank]
Activates a menu which has been previously defined in your program. The
menu will be displayed when the user next presses the right mouse
button, and the options can be selected in the usual way. If a "bank"
number is included with the instruction, then the menu will be taken
from the appropriate memory bank. See MAKE MENU BANK for more details.
MENU OFF (temporarily deactivate a menu) 221
MENU OFF
THis is the opposite of the MENU ON command. It temporarily freezes the
action of the entire menu. The menu can be restared at any time using
the MENU ON command.
MENU DEL (delete one or more menu items)
Erases the selected menu from the Amiga's memory and restores the space
to the rest of your program. There are two possible formats.
MENU DEL
Erases the enitre menu. WARNING! This command is irrevocable!
MENU DEL(,,)
Deletes just a section of the menu. The (,,) parameters contain a list
up to eight values separated by commas. These indicate the precise
position of the item in the menu hierarchy. For example:
Menu Del(1) : Rem Erase title number 1
Menu Del(1,2) : Rem Erase option 2 of title 1
MENU TO BANK (save the menu definitions
in a memory bank)
MENU TO BANK n
This instruction allows you to save an entire menu tree into memory
bank n. If bank n already exist, you'll get a "bank already reserved"
error.
Once you've stored a menu in this way, it will be saved automatically
along with your Basic program. By storing your menu definitions in a
memory bank, you can reduce the size of your program listings
significantly. This will free valuable space in the editors memory, and
will allow you to write longer Basic programs using exactly the same
amount of memory.
BANK TO MENU (restores a menu definition
saved in a menu bank)
BANK TO MENU n
Sets up a menu definition from menu data stored in bank number n. You
menu will be restored to exactly the same state as it was originally
saved. If the menu is complex, this process may take a little time. To
activate your ne menu call the MENU ON instruction.
MENU CALC (recalculate a menu) 222
MENU CALC
One of the nicest features of AMOS menus is that they can be easily
changed during the course of a program. After you've created your
initial definition you can add new items and replace existing options
as well.
Al your menu items are automatically repositioned when the menu is
selected with the right mouse button. If your menus are extremely large
this may takek a little time. MENU CALC allows you to perform this
process at the most appropriate point in your program, and avoid
unnecessary and unwanted delays.
Note that in order to stop the user calling the menu while it's being
changed, you are strongly adviced to freeze the menus with MENU OFF at
the start of your procedure. The menu can then be safely restarted
using the MENU ON command after you've finished. Evolving menus are
particularly useful for adventure games as each location can have its
own individul menu options which can be updated depending on the
player's actions.
Embedded menu commands
======================
Any menu string can optionally include a powerful set of embedded
commands which allow you to customize the appearance of your menus to
an incredible degree. The list of commands in enclosed between sets of
round brackets () and individual instructions are separated using
colons ":". For example:
Menu$(1)="(Locate 10,10 : Ink 1,1) Hello"
Each instruction consists of just two characters which can be in either
upper or lower case. Anything else will be ingnored completely. Most
commands also require you to input one or more commands. These numbers
*must never* make use of expressions as these are not evaluated. The
commands are listed below.
Note: In the syntax the two important characters which make up the
command are in upper case and highlighted bold.
BOB (draw a bob)
BOb n
--
The BOB command draws a bob number n at the current cursor position. No
accound is taken of the hot spot of the bob. All coordinates are
measured relative to the top left corner. Also note that colour zero is
usually treated as transparent. This may be changed using the NOMASK
command from AMOS Basic. For example:
Load "AMOS_DATA:Sprites/Octopus.abk"
Menu$(1)="(Bob 1) 1":Menu$(1,1)="(Bob 2) 2"
Menu$(1,2)="(Bob 3) 3"
Menu On : Wait Key
ICON (draw an icon)
ICon n
--
Draws icon # n at the current cursor position. Note that unlike bobs,
colour zero is NOT normally transparent. See the Basic MAKE ICON MASK
for more details.
LOCATE (move the graphics cursor) 223
LOcate x,y
--
Tis command moves the graphics cursor to coordinates x,y measured
relative to the top left corner of the menu line. Note that after an
instruction the graphics cursor will always be positioned at the bottom
right of the object which has just been drawn. These coordinates will
also be used to determine the location of any further items in your
menu like so:
Menu$(1)="Example ":Menu$(1,1)="Locate (Lo 50,50) in action "
Menu$(1,2)="Guess my coords"
Menu On : Wait Key
INK (set Ink and Paper colours)
INk n,value
--
The INK command assigns the colour indexes to be used for the PEN,
PAPER and OUTLINE colours, Here's a list of the various possibilities:
n Effect
- ------
1 Set text PEN colour
2 Set PAPER colour
3 Set OUTLINE colour
SFONT (set font)
SFont n
--
SFont sets the current font to *graphics* font number n. This will be
used in all future menu items. NOte that you MUST call GET FONTS before
this instruction is executed, otherwise it can only use the two rom
fonts. See EXAMPLE 16.5.
SSTYLE (set font style)
SStyle n
--
This command sets the style of the current font to n which is a
bit-pattern in the following format:
Bit Effect
--- ------
0 Underline
1 Bold
2 Italic
LINE (draw a line) 224
LIne x,y
--
The LINE command draws a line from the current cursor position to the
graphics coordinates x,y. See EXAMPLE 16.6
SLINE (set line pattern)
SLine p
--
Sets the line style used in all subsequent LINE comands to the bit
pattern held in p. Since there is no expession evaluation, this pattern
should always be converted into decimal notation before use. A simple
demonstration of the possible line styles can be found in EXAMPLE 16.7.
BAR (draw a bar)
BAr x,y
--
This draws a rectangular bar from the current cursor coordinates to
x,y. See EXAMPLE 16.8.
OUTLINE (enclose bar with an outline)
OUtline flag
--
Draws a border in the current outline colour (ink 3) around all
subsequent bars. A value of one activates the border and 0 removes it.
ELLIPSE (draw an ellipse)
ELlipse r1,r2
--
Draws an oval with radii r1 and r2 at the current cursor coordinates.
To draw a circle, set r1 equal to r2. See example 16.9.
PROC (call a procedure) 225
PRoc NAME
--
The PROC instruction allows you to call any AMOS Basic procedure
directly within a menu line. The called procedure must NOT include
paramters, otherwise a syntax error will be indicated.
This command allows you to customize the menu precisely to your own
needs without having to limit yourself to the available menu commands.
In order to exploit these features, you'll need to understand a little
bit of theory.
At the start of your procedure the following values are held in the
68000's processor registers.
Dreg(0) X-Coord
This holds the graphical X coordinate of the top left corner of the
current menu item. Don't draw your gfxs over the part of the screen
to the left of this point as this will confuse the menu redrawing
process and may lead to unwanted effects.
Dreg(1) Y-Coord
Contains the Y coordinate of your menu item. As with the X coordinate
you should always limit your drawing operations to the region below
this point to avoit possible errors.
Dreg(2) Status of drawing operations
This register holds the current status of the menu operations. If it
contains a value of 0 (false) the menu item is being drawn. In this
case you will need to load Dreg(0) and Dreg(1) with the coordinates
of the bottom right corner of your menu zone and return from the
procedure immediately. If Dreg(0) is -1 (true) you are free to
perform your gfx operations used by your procedure. After you have
finished you should return the coordinates of the bottom right corner
of your item in Dreg(0) and Dreg(1) as before.
Dreg(3) Status of menu item
D3 is loaded with a value of -1 if the menu is highlighted and the
first menu string is displayed, otherwise it will contain a value 0.
Dreg(4)
D4 is set to TRUE when the menu branch is initially opened.
Areg(1) Address of reserved zone
This is the address of the zone created with RESERVE. It's used to 226
allow several procedures to communicate with each other. See RESERVE
for more details.
The general structure of a menu procedure is:
Procedure ITEM
If DREG(2)
X=DREG():Y=DREG(1)
...draw the item...
Endif
DREG(0)=BX
DREG(1)=BY
End Proc
The dimensions of the menu item as displayed on the screen are set
using the coordinates BX and BY. These MUST be loaded into registers D0
and D1 before leaving your procedure as they are needed to create the
final menu bar.
While inside your procedure you can perform most AMOS instructions
including other procedures. But some instructions are absolutely
forbidden! If you use these commands, you won't get an error message
but your AMIGA may crash unexpectedly!
* NEVER change the current screen inside a menu.
* Don't set or reset a screen zone
* Avoid using instructions such as WAIT, WAIT KEY, INPUT or INKEY$
* Disc operations are absolutely forbidden!
* Any error trapping in your procedure will be ignored.
Used with caution, the PROC command can procedure some mind-blowing
effects. For a demonstration, load EXAMPLE 16.10.
RESERVE (reserve a local data
area for a procedure)
REserve n
--
Reserves n bytes of memory for this menu item. This area can be
accessed from within your menu procedure using the address held in
AREG(1). The data area you have created is common to all the strings in
the current menu object. It can be used to exchange parameters between
the various procedures called by a menu item.
MENU CALLED (redraw a menu item continually)
MENU CALLED(,,)
Automatically redraws the selected menu item 50 times a second whenever
it's displayed on the screen. It's usually used in conjunction with a
menu procedure to generate animated menu items which change in front of 227
your eyes.
In order to make use of this function, you first need to define a
menu procedure, using the principles outlined above. Then add a call to
this procedure in the required title strings using an embedded
MENU CALL. When the user displays the chosen item, your procedure will
be repeatedly accessed by the menuing system.
Since your procedure will be called 50 times a second, it should
obviously return back to the menu as quickly as possible. This will
allow enough time for the rest of the menu to be succesfully updated.
Also note that your embedded procedure can safely animate your item
using either bobs or sprites. However, as the menu items are NOT double
buffered, your bobs may flicker slightly on the screen. So it may be
better to use computed sprites for this purpose instead. Another
approach is to draw your display with the standard AMOS graphics
commands. An example of this can be seen in EXAMPLE 16.11.
MENU ONCE (turns off automatic redrawing)
MEUN ONCE(,,)
Turns off the automatic updating system started using the MENU CALLED.
Alternative menu styles
=======================
Normally the titles of a menu are displayed as a horizontal line and
the options are arranged below it in a vertical menu bar. If you want
to create something a little unusual, you can change the format of each
level of your menu using the following three instructions:
MENU LINE (display a menu
as a horizontal line of items)
MENU LINE level
MENU LINE(,,)
Displays the menu options at the requested level in the form of a
horizontal line. This menu line starts from the left-hand corner of the
first title and stretches to the bottom right corner of the last.
MENU LINE level
Defines the menu style of an entire level of your menu. This sould only
be called during your menu definitions.
MENU LINE (,,)
Normally one would only use the "level" version for this command.
Setting individual items to Line and Bar can give bizarre results, but
this may be useful for something!
MENU TLINE (display a menu as a total line) 228
MENU TLINE level
MENU TLINE(,,)
Displays a section of the menu as a "total line" stretching from the
very left of the screen to the very right. The entire line will be
drawn even when the rist item is in the middle of the screen.
"level" is a number ranging from 1 to 8 which specifies the part of
the menu to be affected. This is the standard form of the instruction,
and should be called during your menu definitions as otherwise it will
have no effect.
You can also change the appearance of a menu after it has been vrated
using a second form of this command. For example,
Menu Line(1,1) : Rem Displays menu 1,1 as a line.
MENU BAR (display a section of the
menu as a bar)
MENU BAR level
MENU BAR(,,)
This displays the selected menu items in the form of a vertical bar.
The width of this bar is automatically set to the dimensions of the
largest item in your menu.
"level" is a number which indicates which part of the current menu
definition is to be affected. As a default this option is used for
levels 2 to 8 in your menu. Note that this form of the MENU BAR
instruction may only be used during your programs initialisation phase.
(,,) is a list of parameters which allow you to change the style of
your menus once they've been installed. Here's an example of Menu Bar
and Menu Tline:
FLAG=0
SET_MAN
Do
If Choice and Choice(1)=2 And Choice(2)=1 Then ALTER
Loop
Procedure SET_MEN
Menu$(1)=" Bar Demo " : Menu$(2)=" Select Below "
Menu$(1,1)=" I do nothing! "
Menu$(2,1)=" Yes, press on me! "
Menu On
End Proc
Procedure ALTER
Shared ALTER
Menu Del
If FLAG=0 Then Menu Bar 1 : Flag=1 Else Menu Tline 1 : Flag=0
SET_MEN
End Proc
MENU INACTIVE (turn off menu item) 229
MENU INACTIVE level
MENU INACTIVE(,,)
As its name suggests, MENU INACTIVE deactivates a series of options in
your menu. Any subsequent attempts to select these items will be
completely ignored. "level" allows you to deactivate an entire section
of the menu and you can also deactivate individual menu options with
the parameters (,,). These indicate the precise position of your item
in the current menu hierarchy.
Note that the menu items you've turned off with the instruction will
be immediately replaced by the INACTIVE$ string you specified during
your original menu definition. If this was omitted, any unavailable
menu options will be shown in italics.
MENU ACTIVE (activate a menu item)
MENU ACTIVE level
MENU ACTIVE(,,)
Simply reverses the effect of a previous MENU INACTIVE command. After
you've called this instruction, the selected options will automatically
redisplayed using their original title strings.
Moveable menus
==============
AMOS menus can be displayed at any point on the screen. Menus can be
moved either explicity by your program or directly by the user.
MENU MOVABLE (activate automatic menu movement)
MENU MOVABLE level
MENU MOVABLE(,,)
Informs the menuing system that the menu items at "level" may be moved
directly by the user - this is the default.
The second form of this command allows you to set the status of each
individual item in the menu. The parameters between the brackets can
indicate any position in the menu hierarchy.
Any menu may be repositioned by moving the mouse pointer over the
FIRST item in the menu and pressing the left mouse button. A
rectangular box will now appear around the selected menu item, and this
may be moved to nay point on the current screen. When you release the
left button the menu will be redrawn at the new position along with all
the associated menu items.
Note that this command does not allow you to change the arrangement
of any items below this level. If you want to manipulate the individual
menu options you'll need to use a seaparate MENU ITEM command. See
EXAMPLE 16.12 for a demonstration of this system.
MENU STATIC (fix a menu into place) 230
MENU STATIC level
MENU STATIC(,,)
Defines the menu at "level" to be immoveable by the user. One problem
with moveable menu is that the amount of the memory they consume will
change during the course of a program. If your menus are particularly
large, or if memory is running tight, this can cause real problems as a
single careless action by the user will abort your program with an
"out of memory" error. With the help of the MENU STATIC command you can
avoid this difficulty completely.
MENU ITEM MOVABLE (move
individual menu options)
MENU ITEM MOVABLE level
MENU ITEM MOVABLE(,,)
This command is similar to MENU MOVABLE except that it allows you to
re-arragne the various options in a particular level. So all the items
in a menu bar may been individually repositioned by the user.
Normally it's illefal to move the items outside the current menu bar,
but this can be overridden using the MENU SEPARATE command.
In order for the menu items to be moveable, the WHOLE menu bar must
also be moveable. So if you fix the MENU into palce with MENU STATIC,
this command will have no effect. Additionally you can't move the first
item in the menu bar as this will move the entire line. Another side
effect is that moving the last menu item will permanently reduce the
size of your menu bar. There are two possible solutions:
* Enclose your entire bar with a rectangular box like so:
Menu$(1,1)=,,,"(Bar 40,100)(Loc 0,0)"
Where MENU$(1,1) is the first item in your current bar.
* Set the last item into place with MENU ITEM STATIC.
MENU ITEM STATIC (static menu item)
MENU ITEM STATIC level
MENU ITEM STATIC(,,)
This command locks one or more menu items firmly into place and is the
default setting.
MENU SEPARATE (separate a list of menu items) 231
MENU SEPARATE level
MENU SEPARATE(,,)
Tells AMOS to separate all the items in the current level. Each item in
your menu istreated completely independently from the previous one. If
you haven't defined a background string, each item will be offset by
two pixels from the one above. This creates an attractive stepped
effect which can be removed by editing the menu with the MENU
Accessory.
The optional parameters to this instruction allow you to split a menu
bar at any point in the line. Once you've separated an item it will be
affected by the MENU MOVABLE commands rather than ITEM instructions.
MENU LINKED (link up a set of menus)
MENU LINKED level
MENU LINKED(,,)
This links one or more menu items together. It's the opposite of the
MENU SEPARATE instruction.
=MENU X (return the graphical X coordinate
of an menu item)
x=MENU X(,,)
The MENU X function allows you to retrieve the position of a menu item
relative to the previous option on the screen. You can use this
information to implement powerful menus such as the one found in
EXAMPLE 16.13.
=MENU Y (return the graphical Y coordinate
of a menu item)
x=MENU Y(,,)
Returns the Y coordinate of a menu option. note that all coordinates
are measured relative to the previous item. So this is NOT a standard
screen coordinate!
Moving a menu within a program
==============================
MENU BASE (move the starting point of a menu)
MENU BASE x,y
This command moves the starting point of the first level of your menus
to the absolute csreen coordinates x,y. All subordatine menu items will
be displayed at their curent positions relative to the top of your
menu. See EXAMPLE 16.14 for a demonstration of the MENU BASE command in
action.
SET MENU (move a menu) 232
SET MENU (,,) TO x,y
Sets the coords of the top left corner of a menu item. These
coordinates are measured relative to the previous level. The starting
point for the entire menu (coords 0,0) may be set with the MENU BASE
command.
All the lvels of the menu below your menu wlil also be moved by this
instruction. Their relative positons will be unchanged. SInce x,y can
be negative numbers, it's possible to arrange the items in a menu bar
in the form of a control panel - see EXAMPLE 16.15.
Displaying a menu at the cursor position
========================================
MENU MOUSE (display the menu under the mouse)
MENU MOUSE ON/OFF
The MENU MOUSE features automatically display all menus starting from
the current position of the mouse cursor. The mouse coordinates are
added to the MENU BASE to get the final position, so it's possible to
place the menu a fixed distance away from the mouse pointer if
required. See EXAMPLE 16.16.